package appFramework

import (
	"accx/appFramework/m_config"
	"accx/appFramework/m_database/mysql"
	mylog "accx/appFramework/m_log"
	"accx/appFramework/server"
	"database/sql"
	"log"

	"github.com/cihub/seelog"
	_ "github.com/go-sql-driver/mysql"
	"golang.org/x/sync/errgroup"
)

var (
	g errgroup.Group
)

type App struct {
	// Router     *Router
	Servers    []server.ServerIf
	ConfigPath string
	Config     *m_config.AppConfig
}

func (app *App) Initialize() error {
	// Init the m_log m_config from the file
	mylog.SetupLogger(app.Config.LogConfigPath)

	// Init the servers
	for index, s := range app.Servers {
		err := s.Initialize(&g, app.Config, index)
		if err != nil {
			return err
		}
	}
	//create database
	dbTest, err := sql.Open("mysql", "root:"+app.Config.MySqlPassword+"@tcp"+"("+app.Config.MySqlHost+":3306)/")
	defer dbTest.Close()
	if err != nil {
		seelog.Error("Connect to  mysql failed:", err)
	} else {
		createdbsql := "CREATE DATABASE " + app.Config.MySqlDb
		dbTest.Exec(createdbsql)
	}
	// connect to mysql
	err = mysql.Initialize(app.Config.MySqlHost, app.Config.MySqlUser,
		app.Config.MySqlPassword, app.Config.MySqlDb)
	if err != nil {
		seelog.Error("Initialize mysql failed:", err)
	}
	db := mysql.GetMysqlDbInstance()

	// Migrate the database
	err = db.Set("gorm:table_options", "ENGINE=InnoDB").AutoMigrate()
	if err != nil {
		seelog.Error(err)
	}
	return nil
}

func (app *App) Start() {
	//err := app.Router.Run(app.Router.Ip + ":" + app.Router.Port)
	var err error
	for _, s := range app.Servers {
		s.Start()
	}
	if err = g.Wait(); err != nil {
		log.Fatal(err)
	}
}

func (app *App) AddServer(s server.ServerIf) {
	app.Servers = append(app.Servers, s)
}

func NewApp(config *m_config.AppConfig) *App {
	return &App{Config: config}
}

func (app *App) Cleanup() {
	db, err := mysql.GetMysqlInstance()
	if err != nil {
		seelog.Error(err)
	}
	err = db.Close()
	if err != nil {
		seelog.Error(err)
	}
}
